package com.xcdh.base.controller;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.xcdh.commons.model.PrimaryId;
import com.xcdh.domain.RequestPage;
import com.xcdh.domain.vo.*;
import com.xcdh.base.service.MenuService;
import com.xcdh.commons.controller.BaseController;
import com.xcdh.domain.entity.MenuDO;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.io.Serializable;
import java.util.*;
import java.util.stream.Collectors;
import java.util.stream.IntStream;

@RestController
@RequestMapping("/menu")
public class MenuController extends BaseController<MenuDO , MenuService>{

    @Autowired
    private MenuService menuService ;

    @PostMapping("/menuList")
    public R<PageVO<MenuTreeVo>> treeMenu(@RequestBody RequestPage<MenuDO> query){
        IPage<MenuDO> page = menuService.list(query);
        return R.page(page.getTotal() , doToVo(page.getRecords() ,0)) ;
    }

    @PostMapping("/asideMenuTree")
    public R<List<MenuTreeVo>> asideMenuTree(@RequestBody MenuDO query){
        List<MenuDO> list = menuService.asideMenuTree(query);
        return R.okData( doToVo(list ,0)) ;
    }



    private List<MenuTreeVo> doToVo(List<MenuDO> menuDOS , int index){
        List<MenuTreeVo> menuTreeVos = new ArrayList<>(menuDOS.size()) ;
        for (MenuDO menuDO : menuDOS) {
            index++ ;
            MenuTreeVo menuTreeVo = TypeValueA2B.a2b(menuDO, MenuTreeVo.class);
            menuTreeVos.add(menuTreeVo) ;
            List<MenuTreeVo> children = doToVo(menuDO.getChildren(), 0);
            menuTreeVo.setChildren(children);
            menuTreeVo.setIndex(index);
            menuTreeVo.setId(menuDO.getMenuId());
        }
        return menuTreeVos ;
    }

    @RequestMapping("/getMenuTree")
    public R getMenuTree(MenuDO menuDO){
        List<MenuDO> list = menuService.lambdaQuery().eq(MenuDO::getType,"0").list();
        return buildTree(list) ;
    }


    @Override
    public R<Void> deleteById(@PathVariable Long id) {
        List<MenuDO> list = menuService.lambdaQuery().eq(MenuDO::getParentId,id).list();
        if(list.isEmpty()){
            return super.deleteById(id);
        }
        return R.error("存在子菜单不可删除");
    }

    private R buildTree(List<MenuDO> list){
         List<MenuTreeVo> treeList = IntStream.range(0, list.size())
                .mapToObj(i -> {
                    MenuDO m = list.get(i);
                    MenuTreeVo vo = TypeValueA2B.a2b(m, MenuTreeVo.class);
                    vo.setIndex(i);
                    vo.setId(m.getMenuId());
                    return vo;
                }) .collect(Collectors.toList());
        Map<Long,List<MenuTreeVo>> hashData = new HashMap<>();
        for (MenuTreeVo tree : treeList) {
            Long parentId = tree.getParentId();
            if(!hashData.containsKey(parentId)){
                hashData.put(parentId , new ArrayList<>()) ;
            }
            hashData.get(parentId).add(tree) ;
        }
        for (MenuTreeVo tree : treeList) {
            Long menuId = tree.getId();
            if(hashData.containsKey(menuId)){
                tree.setChildren(hashData.get(menuId));
                hashData.remove(menuId) ;
            }
        }
        List<MenuTreeVo> result = new ArrayList<>() ;
        for (List<MenuTreeVo> value : hashData.values()) {
            result.addAll(value) ;
        }
        Map<String,Object> resMap = new HashMap<>() ;
        resMap.put("menuTree",result) ;
        resMap.put("sources",treeList) ;
        return R.okData(resMap) ;
    }


}
